package com.niiwoo.civet.account.service.dubbo;

import com.alibaba.dubbo.config.annotation.Reference;
import com.alibaba.dubbo.config.annotation.Service;
import com.alibaba.dubbo.rpc.RpcContext;
import com.alibaba.fastjson.JSON;
import com.niiwoo.asset.org.business.constants.OrgRabbitConstant;
import com.niiwoo.asset.org.business.dto.mq.BankCardRebindNotifyDTO;
import com.niiwoo.asset.service.manager.R360LoanCommonDubboService;
import com.niiwoo.civet.account.dao.entity.*;
import com.niiwoo.civet.account.dao.mapper.OpenAccountRecordMapperExt;
import com.niiwoo.civet.account.dto.common.BankCardDTO;
import com.niiwoo.civet.account.dto.common.BankCardRebindOrderDTO;
import com.niiwoo.civet.account.dto.common.BankTypeDTO;
import com.niiwoo.civet.account.dto.common.PayChannelDTO;
import com.niiwoo.civet.account.dto.common.sendmessage.SendMessageDTO;
import com.niiwoo.civet.account.dto.request.*;
import com.niiwoo.civet.account.dto.response.*;
import com.niiwoo.civet.account.enums.*;
import com.niiwoo.civet.account.service.bankcard.BankCardDubboService;
import com.niiwoo.civet.account.service.local.*;
import com.niiwoo.civet.account.service.withholdProtocol.WithholdProtocolDubboService;
import com.niiwoo.civet.base.constant.OrgConstant;
import com.niiwoo.civet.base.enums.DelFlagEnum;
import com.niiwoo.civet.trade.enums.ProjectFromSourceEnum;
import com.niiwoo.civet.trade.service.configure.TradeConfigDubboService;
import com.niiwoo.civet.trade.service.loan.SpeedLoanDubboService;
import com.niiwoo.civet.trade.service.project.ProjectDubboService;
import com.niiwoo.civet.user.dto.response.UserBasicInfoResponseDTO;
import com.niiwoo.civet.user.service.FadadaDubboService;
import com.niiwoo.civet.user.service.UserBasicInfoDubboService;
import com.niiwoo.tripod.base.component.PrivacyMasks;
import com.niiwoo.tripod.lanmao.component.LanMaoDirectService;
import com.niiwoo.tripod.lanmao.component.LanMaoGatewayService;
import com.niiwoo.tripod.lanmao.component.LanMaoSequence;
import com.niiwoo.tripod.lanmao.enums.AuditTypeEnum;
import com.niiwoo.tripod.lanmao.enums.LanMaoErrorCodeEnum;
import com.niiwoo.tripod.lanmao.enums.TradeQueryTypeEnum;
import com.niiwoo.tripod.lanmao.enums.UserRoleEnum;
import com.niiwoo.tripod.lanmao.request.ExchangeCardAuditRequest;
import com.niiwoo.tripod.lanmao.request.QueryTransactionRequest;
import com.niiwoo.tripod.lanmao.response.ExchangeCardAuditResponse;
import com.niiwoo.tripod.lanmao.response.QueryUpdateBankcardAuditResponse;
import com.niiwoo.tripod.provider.exception.BizException;
import com.niiwoo.tripod.service.component.SnowflakeIdWorker;
import lombok.extern.slf4j.Slf4j;
import org.apache.commons.lang3.StringUtils;
import org.apache.commons.lang3.time.DateUtils;
import org.assertj.core.util.Strings;
import org.joda.time.DateTime;
import org.springframework.amqp.rabbit.core.RabbitTemplate;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.util.Assert;
import org.springframework.util.CollectionUtils;

import java.time.LocalDateTime;
import java.time.LocalTime;
import java.time.ZoneId;
import java.time.format.DateTimeFormatter;
import java.time.temporal.ChronoUnit;
import java.util.*;
import java.util.concurrent.CompletableFuture;

/**
 * Created by wangjichao on 2017/11/8.
 */
@Service(version = "1.0.0")
@Slf4j
public class BankCardDubboServiceImpl implements BankCardDubboService {
    @Autowired
    private BankCardService bankCardService;

    @Autowired
    private AccountService accountService;

    @Autowired
    private PrivacyMasks privacyMasks;

    @Autowired
    private LanMaoSequence lanMaoSequence;

    @Autowired
    private SnowflakeIdWorker snowflakeIdWorker;

    @Autowired
    private LanMaoDirectService lanMaoDirectService;

    @Autowired
    private PayChannelService payChannelService;

    @Autowired
    private BankTypeService bankTypeService;

    @Autowired
    MessageSendLocalService messageSendLocalService;

    @Reference(version = "1.0.0")
    private SpeedLoanDubboService speedLoanDubboService;

    @Reference(version = "1.0.0")
    private ProjectDubboService projectDubboService;

    @Reference(version = "1.0.0")
    private TradeConfigDubboService tradeConfigDubboService;

    @Reference(version = "1.0.0")
    private R360LoanCommonDubboService r360LoanCommonDubboService;

    @Reference(version = "1.0.0")
    private UserBasicInfoDubboService userBasicInfoDubboService;

    @Autowired
    RabbitTemplate rabbitTemplate;

    @Autowired
    OpenAccountRecordMapperExt openAccountRecordMapperExt;

    @Autowired
    private AccountPersonService accountPersonService;
    @Autowired
    private AccountCompanyService accountCompanyService;

    @Autowired
    private WithholdProtocolDubboService withholdProtocolDubboService;

    @Autowired
    LanMaoGatewayService lanMaoGatewayService;

    @Reference(version = "1.0.0")
    private FadadaDubboService fadadaDubboService;

    @Override
    public List<BankTypeDTO> getSupportBankTypeList() {
        //查询银行列表
        List<BankType> bankTypeList = bankCardService.getSupportBankTypeList();

        //查询支持代扣银行列表
        List<Long> supportWithholdList = bankCardService.getWithholdBankList();

        BankTypeDTO bankTypeDTO = null;
        List<BankTypeDTO> bankTypeDTOList = new ArrayList<BankTypeDTO>();
        for (BankType bankType : bankTypeList) {
            bankTypeDTO = new BankTypeDTO();
            bankTypeDTO.setBankTypeId(bankType.getId());
            bankTypeDTO.setBankCode(bankType.getBankCode());
            bankTypeDTO.setBankName(bankType.getBankName());
            bankTypeDTO.setSequence(bankType.getSequence());
            bankTypeDTO.setIsSupportWithhold(false);
            bankTypeDTO.setIsRecommend(bankType.getIsRecommend());
            if(supportWithholdList.contains(bankType.getId())){
                bankTypeDTO.setIsSupportWithhold(true);
            }
            bankTypeDTO.setIsMaintain(bankType.getMaintainStatus() == 1 ? true : false);
            bankTypeDTOList.add(bankTypeDTO);
        }
        return bankTypeDTOList;
    }

    @Override
    public List<BankTypeDTO> getSupportBankTypeListByPC() {
        //查询银行列表
        List<BankType> bankTypeList = bankCardService.getSupportBankTypeListByPC();

        //查询支持代扣银行列表
        List<Long> supportWithholdList = bankCardService.getWithholdBankList();

        BankTypeDTO bankTypeDTO = null;
        List<BankTypeDTO> bankTypeDTOList = new ArrayList<BankTypeDTO>();
        for (BankType bankType : bankTypeList) {
            bankTypeDTO = new BankTypeDTO();
            bankTypeDTO.setBankTypeId(bankType.getId());
            bankTypeDTO.setBankCode(bankType.getBankCode());
            bankTypeDTO.setBankName(bankType.getBankName());
            bankTypeDTO.setSequence(bankType.getSequence());
            bankTypeDTO.setIsSupportWithhold(false);
            if(supportWithholdList.contains(bankType.getId())){
                bankTypeDTO.setIsSupportWithhold(true);
            }
            bankTypeDTO.setIsMaintain(bankType.getMaintainStatus() == 1 ? true : false);
            bankTypeDTOList.add(bankTypeDTO);
        }
        return bankTypeDTOList;
    }

    @Override
    public void unbindCompanyBankCard(UnbindCompanyBankCardRequestDTO unbindCompanyBankCardRequestDTO) {
        Date now=new Date();
        //1.初始化解绑订单;
        UnbindBankCardOrder unbindBankCardOrder=new UnbindBankCardOrder();
        unbindBankCardOrder.setRequestNo(unbindCompanyBankCardRequestDTO.getRequestNo());
        unbindBankCardOrder.setPlatformUserNo(unbindCompanyBankCardRequestDTO.getPlatformUserNo());
        unbindBankCardOrder.setCreateTime(now);
        unbindBankCardOrder.setExpireTime(new DateTime(now).plusMinutes(15).toDate());
        unbindBankCardOrder.setId(snowflakeIdWorker.nextId());
        unbindBankCardOrder.setStatus(UnbindBankCardStatusEnum.IN_HAND.getStatus());
        unbindBankCardOrder.setUserId(unbindCompanyBankCardRequestDTO.getOrgId());

        bankCardService.initUnbindBankCardOrder(unbindBankCardOrder,unbindCompanyBankCardRequestDTO.getRedirectURL());
    }

    @Override
    public UnbindBankCardCallbackResponseDTO unbindCompanyBankCardCallbackSuccess(UnbindCompanyBankCardCallbackRequestDTO unbindCompanyBankCardCallbackRequestDTO) {
        return bankCardService.unbindBankCardCallbackSuccess(unbindCompanyBankCardCallbackRequestDTO);
    }

    @Override
    public UnbindBankCardCallbackResponseDTO unbindCompanyBankCardCallbackFailed(UnbindCompanyBankCardCallbackRequestDTO unbindCompanyBankCardCallbackRequestDTO) {
        return bankCardService.unbindBankCardCallbackFailed(unbindCompanyBankCardCallbackRequestDTO);
    }

    @Override
    public Boolean haveRebindingOrderForOrg(Long accountId) {
        return bankCardService.queryRebindingOrderForCompany(accountId).size()>0;
    }

    @Override
    public RebindCompanyBankCardResponseDTO rebindCompanyBankCard(RebindCompanyBankCardRequestDTO rebindCompanyBankCardRequestDTO) {
        return bankCardService.rebindCompanyBankCardOrder(rebindCompanyBankCardRequestDTO);
    }

    @Override
    public BankTypeDTO getBankTypeByCardBinNo(String cardBinNo) {
        Assert.hasText(cardBinNo, "cardBinNo is inquired");
        BankTypeDTO bankTypeDTO = null;
        BankType bankType = bankCardService.getBankTypeByCardBinNo(cardBinNo);
        if (bankType != null) {
            bankTypeDTO = new BankTypeDTO();
            bankTypeDTO.setBankTypeId(bankType.getId());
            bankTypeDTO.setBankName(bankType.getBankName());
            bankTypeDTO.setBankCode(bankType.getBankCode());
            bankTypeDTO.setSequence(bankType.getSequence());
        }
        return bankTypeDTO;
    }

    public BankCardDTO getBankCardInfoById(Long id){
        BankCard bankCard = bankCardService.getBankCardInfoById(id);
        return transToBankCardDTO(bankCard);

    }

    @Override
    public GetSimpleUserBankCardResponse getSimpleUserBankCard(String userId) {
        return getSimpleUserBankCard(userId, OrgConstant.NIIWOO_ORG_ID);
    }

    @Override
    public GetSimpleUserBankCardResponse getSimpleUserBankCard(String userId,String orgId) {
        GetSimpleUserBankCardResponse getSimpleUserBankCardResponse = new GetSimpleUserBankCardResponse();
        Boolean hasRebindApply = false; //是否有换绑审核中的记录
        Boolean expectAuditTimeIsToday = null;//预期审核完成时间是否今天
        Date expectAuditTime = null;//预期审核完成时间

        // 账户ID
        List<Long> accountIds = new ArrayList<>();
        //查询用户银行卡信息
        BankCard bankCard;
        if(OrgConstant.NIIWOO_ORG_ID.equals(orgId)){
            List<AccountBase> accountBaseList = accountService.listNiiwooAccountByUserId(userId);
            accountBaseList.stream().forEach(accountBase -> {
                accountIds.add(accountBase.getId());
            });

            bankCard = bankCardService.getSimpleUserBankCard(userId);
        }else{
            AccountBase accountBase = accountService.loadOrgAccount(userId,orgId);
            accountIds.add(accountBase.getId());
            bankCard = bankCardService.getOrgUserBankCard(accountBase.getId());
        }

        if (bankCard == null) {
            throw new BizException("ACC10012");
        }

        //封装银行卡数据
        BankCardDTO bankCardDTO = this.transToBankCardDTO(bankCard);

        //查询换绑卡申请
        BankCardRebindOrder bankCardRebindOrder = bankCardService.getCurrentRebindOrderWithAccountIds(userId,accountIds);
        if (bankCardRebindOrder != null) {
            hasRebindApply = true;
            expectAuditTime = this.getExpectAuditTime(bankCardRebindOrder.getUpdateTime());
            expectAuditTimeIsToday = DateUtils.isSameDay(new Date(), expectAuditTime);
        }

        //封装返回值
        getSimpleUserBankCardResponse.setBankCard(bankCardDTO);
        getSimpleUserBankCardResponse.setHasRebindApply(hasRebindApply);
        getSimpleUserBankCardResponse.setExpectAuditTime(expectAuditTime);
        getSimpleUserBankCardResponse.setExpectAuditTimeIsToday(expectAuditTimeIsToday);
        getSimpleUserBankCardResponse.setSupportWithhold(bankCardDTO.getBankType().getIsSupportWithhold());

        return getSimpleUserBankCardResponse;
    }

    @Override
    public RebindBankCardCheckResponse rebindBankCardCheck(String userId) {
        return rebindBankCardCheck(userId,OrgConstant.NIIWOO_ORG_ID);
    }

    @Override
    public RebindBankCardCheckResponse rebindBankCardCheck(String userId,String orgId) {
        Assert.notNull(userId,"userId is required");
        RebindBankCardCheckResponse response = new RebindBankCardCheckResponse();

        response.setForbidRebind(false);
        response.setRebindForbidReasonEnum(null);

        if(!this.r360CheckPass(userId)){
            response.setForbidRebind(true);
            response.setRebindForbidReasonEnum(RebindForbidReasonEnum.HAS_R360_PROCESS);
        }

        NiiwooBill bill = bankCardService.getExistBillForRebindCheck(userId,orgId);
        if (bill != null) {
            response.setRequireUpload(true);
        } else {
            response.setRequireUpload(false);
        }
        return response;
    }

    /**
     * 是否通过融360相关校验,如果有融360进件中 进件处理中 审核中 投资中的标的，返回false
     * @param userId
     * @return
     */
    private boolean r360CheckPass(String userId){

        UserBasicInfoResponseDTO userBasicInfo = userBasicInfoDubboService.getUserBasicInfo(userId);
        if(Objects.isNull(Optional.ofNullable(userBasicInfo).map(info -> info.getMobileNo()).orElse(null))){
            log.error("R360检查用户进件信息错误:查询用户信息异常,userId: {}",userId);
            return false;
        }
        // 审核中和投资中验证,只针对R360标的(换绑卡只针对R360的标的)
        if(projectDubboService.countProjectNumInApproveAndInvest(userId, ProjectFromSourceEnum.R360) > 0) return false;

        // 进件中和进件处理中验证,存在返回true,不存在返回false
        boolean hasR360OrderInProcess = r360LoanCommonDubboService.isExsitRong360UserPushLoanData(userBasicInfo.getMobileNo());
        return !hasR360OrderInProcess;
    }

    @Override
    public BankCardRebindOrderDTO initBankCardRebindOrder(InitBankCardRebindOrderRequestDTO requestDTO) {
        Assert.notNull(requestDTO, "request object is required");
        Assert.notNull(requestDTO.getUserId(),"userId is required");
        Assert.hasText(requestDTO.getBankAccountNo(), "bankAccountNo is required");
        Assert.hasText(requestDTO.getMobileNo(), "mobileNo is required");

        //查询用户存管账户是否开通
        List<AccountBase> accountBaseList = new ArrayList<>();
        if(OrgConstant.NIIWOO_ORG_ID.equals(requestDTO.getOrgId())){
            accountBaseList = accountService.listNiiwooAccountByUserId(requestDTO.getUserId());
        }else{
            AccountBase accountBase = accountService.loadOrgAccount(requestDTO.getUserId(),requestDTO.getOrgId());
            if(accountBase != null){
                accountBaseList.add(accountBase);
            }
        }
        if (accountBaseList.size() == 0) {
            throw new BizException("ACC10001");
        }
        AccountBase activeAccount = null;

        //判断激活,集团账户换卡换任一子账户都会同步更换，所以取任意子账户
        for (AccountBase accountBase : accountBaseList) {
            if (AccountActiveEnum.ACTIVATED.getValue().equals(accountBase.getImportUserActiva())) {
                activeAccount = accountBase;
                break;
            }
        }
        //如果没有账户激活，提示用户激活流程
        if (activeAccount == null) {
            throw new BizException("ACC10003");
        }

        //融360订单检查
        if(!this.r360CheckPass(requestDTO.getUserId())){
            throw new BizException("ACC10038");
        }

        Boolean needApprove = false;
        List<BankCardRebindOrderAttachment> attachmentList = null;
        List<String> fileUrlList = requestDTO.getFileUrls();
        //判断是否需要人工审核
        NiiwooBill bill = bankCardService.getExistBillForRebindCheck(requestDTO.getUserId(),requestDTO.getOrgId());
        if (bill != null) {
            needApprove = true;
            if (CollectionUtils.isEmpty(fileUrlList)) {
                throw new BizException("ACC10014");
            }
            long fileSize = fileUrlList.stream().filter(fileUrl -> !Strings.isNullOrEmpty(fileUrl)).count();
            if(fileSize == 0){
                //前端有时会传["",""]这种数据过来
                throw new BizException("ACC10014");
            }
            if (StringUtils.isEmpty(requestDTO.getUserDesc())){
                throw new BizException("ACC10024");
            }
        }

        //查询用户旧银行卡信息
        BankCard bankCard;
        if(OrgConstant.NIIWOO_ORG_ID.equals(requestDTO.getOrgId())){
            bankCard = bankCardService.getSimpleUserBankCard(requestDTO.getUserId());
        }else{
            AccountBase accountBase = accountService.getOrgAccount(requestDTO.getUserId(),requestDTO.getOrgId());
            bankCard = bankCardService.getOrgUserBankCard(accountBase.getId());
        }

        if (bankCard == null) {
            throw new BizException("ACC10012");
        }

        //新卡不能与旧卡卡号一致
        if(bankCard.getBankAccountNo().equals(privacyMasks.encryptPrivacy(requestDTO.getBankAccountNo()))){
            throw new BizException("ACC10039");
        }

        //银行类型验证
        BankType bankType = null;
        if(requestDTO.getBankTypeId() != null){
            //查询银行类型
            bankType = bankCardService.getBankTypeById(requestDTO.getBankTypeId());
            if(bankType == null){
                throw new BizException("ACC10013");
            }
        }

        //获取过期时间
        Integer expireMin = 15;


        //换绑卡订单
        Long rebindOrderId = snowflakeIdWorker.nextId();
        Date createTime = new Date();
        Date expireTime = new DateTime(createTime).plusMinutes(expireMin).toDate();
        BankCardRebindOrder rebindOrder = new BankCardRebindOrder();
        rebindOrder.setId(rebindOrderId);
        rebindOrder.setRequestNo(lanMaoSequence.getRequestNo());
        rebindOrder.setUserId(requestDTO.getUserId());
        rebindOrder.setAccountId(activeAccount.getId());
        rebindOrder.setMobileNo(privacyMasks.encryptPrivacy(requestDTO.getMobileNo()));
        rebindOrder.setBankAccountNo(privacyMasks.encryptPrivacy(requestDTO.getBankAccountNo()));
        rebindOrder.setUserDesc(requestDTO.getUserDesc());
        rebindOrder.setOldBankCardId(bankCard.getId());
        rebindOrder.setApplyStatus(BankCardRebindApplyStatusEnum.INIT.getValue());
        rebindOrder.setAuditType(needApprove ? BankCardRebindAuditTypeEnum.MANUAL.getValue() : BankCardRebindAuditTypeEnum.AUTO.getValue());
        rebindOrder.setAuditConfirmStatus(BankCardRebindAuditConfirmStatusEnum.INIT.getValue());
        if(bankType != null){
            rebindOrder.setBankCode(bankType.getBankCode());
            rebindOrder.setBankTypeId(bankType.getId());
        }
        rebindOrder.setCreateTime(createTime);
        rebindOrder.setExpiredTime(expireTime);

        //附件
        BankCardRebindOrderAttachment attachment = null;
        if (fileUrlList != null) {
            attachmentList = new ArrayList<>();
            for (String s : fileUrlList) {
                attachment = new BankCardRebindOrderAttachment();
                attachment.setId(snowflakeIdWorker.nextId());
                attachment.setCreateTime(createTime);
                attachment.setFileUrl(s);
                attachment.setRebindOrderId(rebindOrderId);
                attachmentList.add(attachment);
            }
        }

        //初始化换绑卡订单
        bankCardService.initBankCardRebindOrder(rebindOrder, attachmentList);
        //构建返回值
        BankCardRebindOrderDTO bankCardRebindOrderDTO = new BankCardRebindOrderDTO();
        bankCardRebindOrderDTO.setId(rebindOrder.getId());
        bankCardRebindOrderDTO.setAccountNo(activeAccount.getAccountNo());
        bankCardRebindOrderDTO.setRequestNo(rebindOrder.getRequestNo());
        bankCardRebindOrderDTO.setExpireTime(rebindOrder.getExpiredTime());
        bankCardRebindOrderDTO.setBankAccountNo(privacyMasks.decryptPrivacy(rebindOrder.getBankAccountNo()));
        bankCardRebindOrderDTO.setMobileNo(privacyMasks.decryptPrivacy(rebindOrder.getMobileNo()));

        return bankCardRebindOrderDTO;

    }

    @Override
    public BankCardDTO getUserBankCardInfo(String userId) {
        //查询用户银行卡信息
        BankCard bankCard = bankCardService.getSimpleUserBankCard(userId);
        if (bankCard == null) {
            throw new BizException("ACC10012");
        }
        return getBankCardDTO(bankCard);
    }

    private BankCardDTO getBankCardDTO(BankCard bankCard) {
        BankType bankType = bankTypeService.getBankTypeByCode(bankCard.getBankCode());
        if(bankType == null){
            throw new BizException("ACC10013");
        }
        BankTypeDTO bankTypeDTO = new BankTypeDTO();
        bankTypeDTO.setBankName(bankType.getBankName());
        bankTypeDTO.setBankCode(bankType.getBankCode());
        bankTypeDTO.setIsSupportWithhold(bankCardService.isSupportWithhold(bankType.getId()));
        //封装银行卡数据
        BankCardDTO bankCardDTO = new BankCardDTO();
        bankCardDTO.setBankCardId(bankCard.getId());
        bankCardDTO.setBankType(bankTypeDTO);
        bankCardDTO.setBankAccountNo(privacyMasks.decryptPrivacy(bankCard.getBankAccountNo()));
        bankCardDTO.setIdCard(privacyMasks.decryptPrivacy(bankCard.getIdCard()));
        bankCardDTO.setMobileNo(privacyMasks.decryptPrivacy(bankCard.getMobileNo()));
        bankCardDTO.setRealName(bankCard.getRealName());
        bankCardDTO.setBankCode(bankCard.getBankCode());
        bankCardDTO.setUpdateTime(bankCard.getUpdateTime());
        return bankCardDTO;
    }

    @Override
    public BankCardDTO getUserBankCardByAccountId(Long accountId) {
        //查询用户银行卡信息
        BankCard bankCard = bankCardService.getOrgUserBankCard(accountId);
        if (bankCard == null) {
            throw new BizException("ACC10012");
        }

        return getBankCardDTO(bankCard);
    }

    @Override
    public BankCardRebindCallbackResponseDTO bankCardRebindCallback(BankCardRebindCallbackRequestDTO request) {

        Assert.notNull(request, "request object is required");

        BankCardRebindCallbackResponseDTO responseDTO = new BankCardRebindCallbackResponseDTO();
        BankCardRebindOrder bankCardRebindOrder = bankCardService.getBankCardRebindOrderByRequestNoFromMaster(request.getRequestNo());
        if(bankCardRebindOrder == null){
            throw new BizException("ACC10018");
        }

        //查询回调用户绑定的银行类型
        BankType bankType = bankCardService.getBankTypeByCodeIgnoreStatus(request.getBankCode());

        //返回值公共参数
        responseDTO.setOrderId(String.valueOf(bankCardRebindOrder.getId()));
        responseDTO.setRequestNo(bankCardRebindOrder.getRequestNo());
        responseDTO.setAuditType(BankCardRebindAuditTypeEnum.enumOf(bankCardRebindOrder.getAuditType()));

        //更新业务数据
        BankCardRebindAuditConfirmOrder confirmOrder = null;
        //更新业务数据
        try{
            confirmOrder = bankCardService.bankCardRebindCallbackSuccess(bankCardRebindOrder.getId(),bankType);
        }catch(BizException e){
            log.error("银行卡回调幂等返回:{}", JSON.toJSONString(request));
            //幂等处理，避免前台回调时提示重复操作
            if("ACC10017".equals(e.getErrorCode())){
                responseDTO.setAuditStatus(BankCardRebindAuditStatusEnum.enumOf(bankCardRebindOrder.getAuditStatus()));

                // 设置[开通代扣还款]按钮是否可见
                setIsShowSignWithholdBtn(responseDTO, bankCardRebindOrder.getUserId());

                // 补签《还款服务委托书》
                signRepayAgreementContractForOldUser(responseDTO, bankCardRebindOrder.getUserId());

                return responseDTO;
            }
        }

        //如果存在确认订单说明自动审核,需要后续自动审核接口
        ExchangeCardAuditRequest auditRequest = null;
        CompletableFuture<ExchangeCardAuditResponse> future = null;
        ExchangeCardAuditResponse exchangeCardAuditResponse = null;

        //自动审核调用状态
        Boolean auditInvokeSuccess = false;
        if(confirmOrder!=null){
            auditRequest = new ExchangeCardAuditRequest();
            auditRequest.setRequestNo(confirmOrder.getRequestNo());
            auditRequest.setOriginalRequestNo(bankCardRebindOrder.getRequestNo());
            auditRequest.setAuditType(AuditTypeEnum.PASSED);
            future =lanMaoDirectService.auditExchangeCard(auditRequest);
            try{
                exchangeCardAuditResponse = future.get();
                if(exchangeCardAuditResponse.isSuccess()){
                    auditInvokeSuccess = true;
                }else{
                    log.error("懒猫自动审核失败:{}",JSON.toJSONString(request));
                }
            }
            catch(Exception e){
                log.error("懒猫自动审核接口调用异常:{}",JSON.toJSONString(request),e);
            }
            //如果接口调用超时当作审核中处理，由定时任务进行补单审核
            if(!auditInvokeSuccess){
                responseDTO.setAuditStatus(BankCardRebindAuditStatusEnum.WAITING_APPROVE);
            }else{
                bankCardService.autoAuditRebindOrder(bankCardRebindOrder,confirmOrder,bankType);
                responseDTO.setAuditStatus(BankCardRebindAuditStatusEnum.PASS);
                //发送短信 站内信
                RpcContext.getContext().asyncCall(new Runnable() {
                    @Override
                    public void run() {
                        SendMessageDTO sendMessageDTO = new SendMessageDTO();
                        try {
                            log.info("发送短信/站内信消息-换绑卡审核通过-发送开始：{}", JSON.toJSONString(sendMessageDTO));
                            sendMessageDTO.setUserId(bankCardRebindOrder.getUserId());
                            messageSendLocalService.sendMsgForChangeBankCardAduitPassed(sendMessageDTO);
                            log.info("发送短信/站内信消息-换绑卡审核通过-发送结束：{}", JSON.toJSONString(sendMessageDTO));
                        } catch (Exception e) {
                            log.error("发送短信/站内信消息-换绑卡审核通过-异常：{}", JSON.toJSONString(sendMessageDTO), e);
                        }

                        //通知宏特等资产端换绑卡
                        bankCardRebindOrder.setBankCode(bankType.getBankCode());
                        sendRebindSuccessMsgForOrg(bankCardRebindOrder);
//                        projectDubboService.sendMqToAssetSide(bankCardRebindOrder.getUserId());
                    }
                });

//                try{
//                    // 如果该用户是通过卡牛开户，则通知卡牛
//                    OpenAccountRecord record = openAccountRecordMapperExt.selectByUserIdAndRole(bankCardRebindOrder.getUserId(), UserRoleEnum.BORROWERS.getValue());
//                    log.info("卡牛换绑卡通知###查询开户记录, userId={}, orderId={}, record={}", bankCardRebindOrder.getUserId(), bankCardRebindOrder.getId(), record);
//                    if (record != null && OpenAccountWayEnum.except(record.getOpenAccountWay(), OpenAccountWayEnum.CARD_NIU_PERSON_BIND_BANK_CARD_REGISTER, OpenAccountWayEnum.GROUP_ACCOUNT_CORRELATE)) {
//                        CompletableFuture.runAsync(() -> {
//                            BankCard newestSimpleUserBankCard = bankCardService.getNewestSimpleUserBankCard(bankCardRebindOrder.getUserId());
//                            BankType bankTypeByCode = bankTypeService.getBankTypeByCode(newestSimpleUserBankCard.getBankCode());
//                            JSONObject json = new JSONObject();
//                            json.put("userId", newestSimpleUserBankCard.getUserId());
//                            json.put("orderId", String.valueOf(bankCardRebindOrder.getId()));
//                            json.put("bankCardNo", privacyMasks.decryptPrivacy(newestSimpleUserBankCard.getBankAccountNo()));
//                            json.put("bankCardMobileNo", privacyMasks.decryptPrivacy(newestSimpleUserBankCard.getMobileNo()));
//                            json.put("bankName", bankTypeByCode.getBankName());
//                            log.info("卡牛换绑卡通知###请求, data={}", json.toJSONString());
//                            rabbitTemplate.convertAndSend(MQConstant.CARD_NIU_ACCOUNT_EXCHANGE, MQConstant.CARD_NIU_REBIND_CARD_ROUTING, json.toJSONString());
//                        }).whenComplete((success, throwable) -> {
//                            if (throwable != null) {
//                                log.info(String.format("卡牛换绑卡通知###失败, userId=%s, errorMessage=%s", bankCardRebindOrder.getUserId(), throwable.getMessage()), throwable);
//                            } else {
//                                log.error("卡牛换绑卡通知###成功, userId={}", bankCardRebindOrder.getUserId());
//                            }
//                        });
//                    }
//                }catch(Exception e){
//                    log.error("换绑卡自动审核卡牛通知异常：{}",JSON.toJSONString(bankCardRebindOrder),e);
//                }
            }
        }else{
            responseDTO.setAuditStatus(BankCardRebindAuditStatusEnum.WAITING_APPROVE);
        }

        // 设置[开通代扣还款]按钮是否可见
        setIsShowSignWithholdBtn(responseDTO, bankCardRebindOrder.getUserId());

        // 补签《还款服务委托书》
        signRepayAgreementContractForOldUser(responseDTO, bankCardRebindOrder.getUserId());

        return responseDTO;
    }

    @Override
    public CompanyBankCardRebindCallbackResponseDTO companyBankCardRebindCallback(CompanyBankCardRebindCallbackRequestDTO request) {
        log.info("换绑银行卡回调,请求流水号={},请求参数={}", request.getRequestNo(), JSON.toJSONString(request));
        CompanyBankCardRebindCallbackResponseDTO responseDTO = new CompanyBankCardRebindCallbackResponseDTO();
        BankCardRebindOrder bankCardRebindOrder = bankCardService.getBankCardRebindOrderByRequestNoFromMaster(request.getRequestNo());
        if (bankCardRebindOrder == null) {
            log.error("企业换绑银行卡回调,请求流水号={},换绑银行卡订单不存在", request.getRequestNo());
            throw new BizException("ACC10018");
        }

        AccountCompany accountCompany = accountCompanyService.queryByAccountNo(request.getAccountNo());

        //查询回调用户绑定的银行类型
        BankType bankType = bankCardService.getBankTypeByCodeIgnoreStatus(request.getBankCode());

        //返回值公共参数
        responseDTO.setOrderId(String.valueOf(bankCardRebindOrder.getId()));
        responseDTO.setRequestNo(bankCardRebindOrder.getRequestNo());
        responseDTO.setAuditType(BankCardRebindAuditTypeEnum.enumOf(bankCardRebindOrder.getAuditType()));

        //更新业务数据
        BankCardRebindAuditConfirmOrder confirmOrder = null;
        //更新业务数据
        try {
            confirmOrder = bankCardService.bankCardRebindCallbackSuccess(bankCardRebindOrder.getId(), bankType);
        } catch (BizException e) {
            log.error("企业换绑银行卡回调,请求流水号={},换绑银行卡订单重复操作.", request.getRequestNo());
            //幂等处理，避免前台回调时提示重复操作
            if ("ACC10017".equals(e.getErrorCode())) {
                responseDTO.setAuditStatus(BankCardRebindAuditStatusEnum.enumOf(bankCardRebindOrder.getAuditStatus()));

                return responseDTO;
            }
        }

        //如果存在确认订单说明自动审核,需要后续自动审核接口
        ExchangeCardAuditRequest auditRequest = null;
        CompletableFuture<ExchangeCardAuditResponse> future = null;
        ExchangeCardAuditResponse exchangeCardAuditResponse = null;
        boolean isRebindCard=bankCardRebindOrder.getOldBankCardId()==-1?false:true;

        //自动审核调用状态
        Boolean auditInvokeSuccess = false;
        //如果是换卡，则需要调用换卡审核接口
        if (isRebindCard) {
            log.info("换绑银行卡回调,请求流水号={},换卡操作{}", request.getRequestNo());
            auditRequest = new ExchangeCardAuditRequest();
            auditRequest.setRequestNo(confirmOrder.getRequestNo());
            auditRequest.setOriginalRequestNo(bankCardRebindOrder.getRequestNo());
            auditRequest.setAuditType(AuditTypeEnum.PASSED);
            log.info("换绑银行卡回调,请求流水号={},懒猫自动审核,请求参数={}", request.getRequestNo(), JSON.toJSONString(auditRequest));
            future = lanMaoDirectService.auditExchangeCard(auditRequest);
            try {
                exchangeCardAuditResponse = future.get();
                log.info("换绑银行卡回调,请求流水号={},懒猫自动审核,响应结果={}", request.getRequestNo());
                if (exchangeCardAuditResponse.isSuccess()) {
                    auditInvokeSuccess = true;
                } else {
                    log.info("换绑银行卡回调,请求流水号={},懒猫自动审核失败.", request.getRequestNo());
                }
            } catch (Exception e) {
                log.error("换绑银行卡回调,请求流水号={},懒猫自动审核发生系统异常,原因={}.", request.getRequestNo(), e);
            }
            //如果接口调用超时当作审核中处理，由定时任务进行补单审核
            if (!auditInvokeSuccess) {
                responseDTO.setAuditStatus(BankCardRebindAuditStatusEnum.WAITING_APPROVE);
            } else {
                bankCardService.autoAuditRebindOrder(bankCardRebindOrder, confirmOrder, bankType);
                responseDTO.setAuditStatus(BankCardRebindAuditStatusEnum.PASS);
            }
        }
        //如果是单独绑卡，则不需要调用换卡审核接口;
        else {
            log.info("换绑银行卡回调,请求流水号={},单独绑卡操作{}", request.getRequestNo());
            log.info("换绑银行卡回调,请求流水号={},当前AccountCompany={}", request.getRequestNo(),JSON.toJSONString(accountCompany));
            bankCardService.singleBindCard(accountCompany, bankCardRebindOrder, confirmOrder, bankType);
            responseDTO.setAuditStatus(BankCardRebindAuditStatusEnum.PASS);
        }

        AccountCompany accountCompany2Update = new AccountCompany();
        accountCompany2Update.setAccountId(accountCompany.getAccountId());
        accountCompany2Update.setBankCardNo(privacyMasks.encryptPrivacy(request.getBankAccountNo()));
        accountCompany2Update.setBankCode(request.getBankCode());
        accountCompany2Update.setUpdateTime(new Date());
        accountCompanyService.update(accountCompany2Update);

        return responseDTO;
    }

    /**
     * 是否企业换绑银行卡
     * @param rebindBankCardType
     * @return
     */
    private boolean isCompanyRebindBankCard(Byte rebindBankCardType){
        return rebindBankCardType == null ? false : (rebindBankCardType.equals(BankCardRebindTypeEnum.COMPANY.getType()) ? true : false);
    }

    /**
     * 发送换绑卡成功消息给机构
     * @param bankCardRebindOrder
     */
    private void sendRebindSuccessMsgForOrg(BankCardRebindOrder bankCardRebindOrder){
        log.info("换绑卡自动审核成功机构通知MQ消息发送流程:{}",JSON.toJSONString(bankCardRebindOrder));
        try{
            AccountBase accountBase  = accountService.loadAccountByIdFromMaster(bankCardRebindOrder.getAccountId());
            if(OrgConstant.NIIWOO_ORG_ID.equals(accountBase.getOrgId())){
                return;
            }
            BankCardRebindNotifyDTO bankCardRebindNotifyDTO = new BankCardRebindNotifyDTO();
            bankCardRebindNotifyDTO.setOrgId(accountBase.getOrgId());
            bankCardRebindNotifyDTO.setNiiwooUserId(bankCardRebindOrder.getUserId());
            bankCardRebindNotifyDTO.setRebindOrderId(String.valueOf(bankCardRebindOrder.getId()));
            bankCardRebindNotifyDTO.setBankCardNo(privacyMasks.decryptPrivacy(bankCardRebindOrder.getBankAccountNo()));
            bankCardRebindNotifyDTO.setBankCode(bankCardRebindOrder.getBankCode());
            bankCardRebindNotifyDTO.setMobileNo(privacyMasks.decryptPrivacy(bankCardRebindOrder.getMobileNo()));
            log.info("换绑卡自动审核成功机构通知MQ消息发送:{}",JSON.toJSONString(bankCardRebindNotifyDTO));

            rabbitTemplate.convertAndSend(OrgRabbitConstant.Exchange.ORG_COMMON_DIRECT_EXCHANGE,
                    OrgRabbitConstant.getRoutingKey(OrgRabbitConstant.Exchange.ORG_COMMON_DIRECT_EXCHANGE,
                            OrgRabbitConstant.Queue.BANK_CARD_REBIND_NOTIFY_QUEUE),
                    bankCardRebindNotifyDTO);
            log.info("换绑卡自动审核成功机构通知MQ消息发送成功:{}",JSON.toJSONString(bankCardRebindNotifyDTO));
        }catch(Exception e){
            log.error("换绑卡自动审核成功机构通知MQ消息发送异常：{}",JSON.toJSONString(bankCardRebindOrder),e);
        }
    }

    /**
     * 设置"开通代扣还款"按钮是否可见(0:不显示, 1:显示)
     * @param responseDTO
     */
    private void setIsShowSignWithholdBtn(BankCardRebindCallbackResponseDTO responseDTO, String userId) {
        responseDTO.setIsShowSignWithholdBtn(0);
        try {
            if (BankCardRebindAuditTypeEnum.AUTO.equals(responseDTO.getAuditType())
                    && BankCardRebindAuditStatusEnum.PASS.equals(responseDTO.getAuditStatus())) { // 自动审核通过
                AccountBase borrowAccount = accountService.getNiiwooAccount(userId, UserRoleEnum.BORROWERS);
                if (borrowAccount != null && borrowAccount.getId() != null) { // 有借款账户
                    WithholdProtocolResultDTO withholdProtocolResultDTO = withholdProtocolDubboService.getWithholdProtocolResultForLocal(userId, OrgConstant.NIIWOO_ORG_ID);
                    log.info("setIsShowSignWithholdBtn userId:{}, withholdProtocolResultDTO: {}", userId, JSON.toJSONString(withholdProtocolResultDTO));

                    if (!(Boolean.TRUE.equals(withholdProtocolResultDTO.getResult()) && withholdProtocolResultDTO.getExpire() == 1)) { // 未开通代扣/已失效
                        responseDTO.setIsShowSignWithholdBtn(1);
                    }
                }
            }
        } catch (Exception e) {
            log.error("设置[开通代扣还款]按钮是否可见出错：", e);
        }
    }

    /**
     * 补签《还款服务委托书》
     * @param responseDTO
     * @param userId
     */
    private void signRepayAgreementContractForOldUser(BankCardRebindCallbackResponseDTO responseDTO, String userId) {
        try {
            if (BankCardRebindAuditTypeEnum.AUTO.equals(responseDTO.getAuditType())
                    && BankCardRebindAuditStatusEnum.PASS.equals(responseDTO.getAuditStatus())) { // 自动审核通过
                CompletableFuture.runAsync(() -> {
                    fadadaDubboService.signRepayAgreementContractForOldUser(userId);
                });
            }
        } catch (Exception e) {
            log.error("用户[userId:{}]补签《还款服务委托书》出错：", userId, e);
        }
    }

    @Override
    public PayChannelDTO getUserRechargeChannelByRoute(Long bankTypeId, String userId) {
        Assert.notNull(bankTypeId,"bankTypeId is required");
        Assert.notNull(userId,"userId is required");

        PayChannel payChannel = payChannelService.getUserRechargeChannelByRoute(userId,bankTypeId);
        if(payChannel == null){
            throw new BizException("ACC10020");
        }


        PayChannelBank payChannelBank = payChannelService.getPayChannelBank(payChannel.getId(),bankTypeId);
        if(payChannelBank == null){
            throw new BizException("ACC10021");
        }

        PayChannelDTO payChannelDTO = new PayChannelDTO();
        payChannelDTO.setPayChannelId(payChannel.getId());
        payChannelDTO.setPayChannelCode(payChannel.getChannelCode());
        payChannelDTO.setPayChannelName(payChannel.getChannelName());
        payChannelDTO.setMaxAmountPerDay(payChannelBank.getMaxAmountPerDay());
        payChannelDTO.setMaxAmountPerMonth(payChannelBank.getMaxAmountPerMonth());
        payChannelDTO.setMaxAmountPerTrade(payChannelBank.getMaxAmountPerTrade());

        return payChannelDTO;
    }

    @Override
    public void rebindBankCardJob() {
        QueryTransactionRequest request = null;
        QueryUpdateBankcardAuditResponse response = null;
        CompletableFuture<QueryUpdateBankcardAuditResponse> completableFuture = null;
        AccountBase account = null;
        QueryUpdateBankcardAuditResponse.UpdateBankcardAuditDetail updateBankcardAuditDetail = null;
        BankCardRebindOrder updateRebindOrder = null;
        List<BankCardRebindOrder> orderList = bankCardService.listBankCardForJob();
        if(orderList.size() == 0){
            return;
        }
        log.info("换绑卡补单JOB总记录：{},详情：{}",orderList.size(),JSON.toJSONString(orderList));
        for(BankCardRebindOrder bankCardRebindOrder : orderList){

            try{
                account = accountService.loadAccountById(bankCardRebindOrder.getAccountId());
                //首先查询存管实时状态
                request = new QueryTransactionRequest();
                request.setPlatformUserNo(account.getAccountNo());
                request.setTransactionType(TradeQueryTypeEnum.UPDATE_BANKCARD_AUDIT);
                request.setRequestNo(bankCardRebindOrder.getRequestNo());
                completableFuture =  lanMaoDirectService.queryUpdateBankcardAudit(request);
                try {
                    response = completableFuture.get();
                }
                catch(Exception e){
                    log.error("存管换绑卡订单查询异常：{}",JSON.toJSONString(bankCardRebindOrder),e);
                    continue;
                }
                //超时
                if(LanMaoErrorCodeEnum.QUERY_OBJECT_NOT_EXIST.getCode().equals(response.getErrorCode())){
                    Date now = new Date();
                    if(bankCardRebindOrder.getExpiredTime().before(now)){
                        updateRebindOrder = new BankCardRebindOrder();
                        updateRebindOrder.setId(bankCardRebindOrder.getId());
                        updateRebindOrder.setDelFlag(DelFlagEnum.DELETE.getValue());
                        updateRebindOrder.setUpdateTime(now);
                        bankCardService.updateBankCardRebindOrder(updateRebindOrder);
                    }
                    continue;
                }
                //掉单
                if(response.isSuccess()){
                    if(response.getRecords() == null || response.getRecords().size() == 0){
                        continue;
                    }
                    updateBankcardAuditDetail = response.getRecords().get(0);
                    if(updateBankcardAuditDetail.getAuditStatus() == AuditTypeEnum.AUDIT){
                        //企业换绑卡
                        if(bankCardRebindOrder.getType().equals(BankCardRebindTypeEnum.COMPANY.getType())) {
                            CompanyBankCardRebindCallbackRequestDTO companyBankCardRebindCallbackRequestDTO=new CompanyBankCardRebindCallbackRequestDTO();
                            companyBankCardRebindCallbackRequestDTO.setAccountNo(account.getAccountNo());
                            companyBankCardRebindCallbackRequestDTO.setBankCode(updateBankcardAuditDetail.getBankcode().getCode());
                            companyBankCardRebindCallbackRequestDTO.setBankAccountNo(updateBankcardAuditDetail.getBankcardNo());
                            companyBankCardRebindCallbackRequestDTO.setRequestNo(bankCardRebindOrder.getRequestNo());

                            this.companyBankCardRebindCallback(companyBankCardRebindCallbackRequestDTO);
                        }
                        //个人换绑卡
                        else{
                            BankCardRebindCallbackRequestDTO requestDTO = new BankCardRebindCallbackRequestDTO();
                            requestDTO.setAccountNo(account.getAccountNo());
                            requestDTO.setRequestNo(bankCardRebindOrder.getRequestNo());
                            requestDTO.setBankCode(updateBankcardAuditDetail.getBankcode().getCode());
                            requestDTO.setMobileNo(updateBankcardAuditDetail.getMobile());
                            requestDTO.setBankAccountNo(updateBankcardAuditDetail.getBankcardNo());

                            this.bankCardRebindCallback(requestDTO);
                        }
                        continue;
                    }
                }
            }catch(Exception e){
                log.error("换绑卡补单JOB补单异常：{}",JSON.toJSONString(bankCardRebindOrder),e);
            }
        }
    }


    /**
     * 根据换绑卡提交时间计算预期审核完成时间
     *
     * @param submitDate
     * @return
     */
    private Date getExpectAuditTime(Date submitDate) {
        LocalDateTime expectAuditDateTime = null;
        //提交日期
        LocalDateTime localDateTime = submitDate.toInstant().atZone(ZoneId.systemDefault()).toLocalDateTime();
        //提交时间，去除秒和毫秒
        LocalTime localTime = submitDate.toInstant().atZone(ZoneId.systemDefault()).toLocalTime().withSecond(0).withNano(0);
        //工作时间固定
        DateTimeFormatter df = DateTimeFormatter.ofPattern("HH:mm");
        LocalTime workBeginTime = LocalTime.parse("09:00", df);
        LocalTime workEndTime = LocalTime.parse("18:00", df);
        //工作时间两小时后
        if (localTime.isAfter(workBeginTime) && localTime.isBefore(workEndTime)) {
            expectAuditDateTime = localDateTime.plusHours(2);
        }
        //非工作期次日12点前
        else {
            expectAuditDateTime = localDateTime.plusDays(1).truncatedTo(ChronoUnit.DAYS).plusHours(12);
        }
        return Date.from(expectAuditDateTime.atZone(ZoneId.systemDefault()).toInstant());
    }

    @Override
    public boolean updateBankCardMobileNo(UpdateBankCardMobileNoRequestDTO requestDTO) {
        AccountBase base = accountService.loadAccountByAccountNo(requestDTO.getAccountNo());
        if (!base.getImportUserActiva().equals(AccountActiveEnum.ACTIVATED.getValue())) {
            throw new BizException("ACC10003");// 存管账户未激活
        }

        BankCard card = null;
        if (OrgConstant.NIIWOO_ORG_ID.equals(base.getOrgId())) {
            card = bankCardService.getSimpleUserBankCard(base.getUserId());
        } else {
            card = bankCardService.getOrgUserBankCard(base.getId());
        }

        if (card == null || !privacyMasks.encryptPrivacy(requestDTO.getBankCardNo()).equals(card.getBankAccountNo())) {
            throw new BizException("ACC10012");
        }
        BankCard updateCard = new BankCard();
        updateCard.setId(card.getId());
        updateCard.setUserId(base.getUserId());
        updateCard.setMobileNo(privacyMasks.encryptPrivacy(requestDTO.getBankCardMobileNo()));
        return bankCardService.updateBankCard(updateCard);
    }

    @Override
    public void sendMsgForChangeBankCardAduitPassed(SendMessageDTO sendMessageDTO) {
        messageSendLocalService.sendMsgForChangeBankCardAduitPassed(sendMessageDTO);
    }

    @Override
    public void sendMsgForChangeBankCardAduitNotPassed(SendMessageDTO sendMessageDTO, List<Object> params) {
        messageSendLocalService.sendMsgForChangeBankCardAduitNotPassed(sendMessageDTO, params);
    }

    @Override
    public boolean orgUserBankCardIsMatch(String orgId, String userId, String bankCard) {
        AccountPerson accountPerson = accountPersonService.queryByUserIdAndOrgId(userId, orgId);
        if (accountPerson == null) {
            return false;
        }

        BankCard orgUserBankCard = bankCardService.getOrgUserBankCard(accountPerson.getAccountId());
        if (orgUserBankCard == null) {
            return false;
        }

        if (StringUtils.isEmpty(orgUserBankCard.getBankAccountNo())) {
            return false;
        }

        return orgUserBankCard.getBankAccountNo().equals(bankCard);
    }

    @Override
    public boolean orgCompanyBankCardIsMatch(String orgId, String companyOrgId, String bankCard) {
        AccountCompany accountCompany = accountCompanyService.queryAccountCompanyByOrgIdAndCompanyOrgId(orgId, companyOrgId);
        if (accountCompany == null) {
            return false;
        }

        BankCard orgUserBankCard = bankCardService.getOrgUserBankCard(accountCompany.getAccountId());
        if (orgUserBankCard == null) {
            return false;
        }

        if (StringUtils.isEmpty(orgUserBankCard.getBankAccountNo())) {
            return false;
        }

        return orgUserBankCard.getBankAccountNo().equals(bankCard);
    }

    private BankCardDTO transToBankCardDTO(BankCard bankCard){
        if(Objects.isNull(bankCard)){
            return  null;
        }

        //查询银行类型
        BankType bankType = bankCardService.getBankTypeById(bankCard.getBankTypeId());
        if (bankType == null) {
            throw new BizException("ACC10013");
        }

        BankTypeDTO bankTypeDTO = new BankTypeDTO();
        bankTypeDTO.setBankTypeId(bankType.getId());
        bankTypeDTO.setBankCode(bankType.getBankCode());
        bankTypeDTO.setBankName(bankType.getBankName());
        bankTypeDTO.setIsSupportWithhold(bankCardService.isSupportWithhold(bankType.getId()));
        bankTypeDTO.setRechargeChangeStatus(bankType.getRechargeChangeStatus());
        bankTypeDTO.setIsMaintain(bankType.getMaintainStatus() == 1 ? true : false);

        //封装银行卡数据
        BankCardDTO bankCardDTO = new BankCardDTO();
        bankCardDTO.setBankCardId(bankCard.getId());
        bankCardDTO.setBankAccountNo(privacyMasks.maskBankCard(privacyMasks.decryptPrivacy(bankCard.getBankAccountNo())));
        bankCardDTO.setIdCard(privacyMasks.decryptPrivacy(bankCard.getIdCard()));
        bankCardDTO.setMobileNo(privacyMasks.maskMobile(privacyMasks.decryptPrivacy(bankCard.getMobileNo())));
        bankCardDTO.setRealName(bankCard.getRealName());
        bankCardDTO.setBankType(bankTypeDTO);

        return bankCardDTO;
    }
}
